package com.flyco.modules.returns.controller;

import java.math.BigDecimal;
import java.util.*;
import java.io.IOException;
import java.io.UnsupportedEncodingException;
import java.net.URLDecoder;
import java.util.stream.Collectors;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;

import com.flyco.common.api.vo.Result;
import com.flyco.common.system.query.QueryGenerator;
import com.flyco.common.aspect.annotation.AutoLog;
import com.flyco.common.system.vo.LoginUser;
import com.flyco.common.util.IdGenerator16Bit;
import com.flyco.common.util.oConvertUtils;
import com.flyco.modules.oms.entity.OmsOrderTrace;
import com.flyco.modules.returns.entity.*;
import com.flyco.modules.returns.service.IOmsOrderReturnItemBatchService;
import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.baomidou.mybatisplus.core.metadata.IPage;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.flyco.modules.returns.service.IOmsOrderReturnItemService;
import lombok.extern.slf4j.Slf4j;
import com.flyco.common.system.base.controller.BaseController;
import com.flyco.poi.excel.ExcelImportUtil;
import com.flyco.poi.excel.def.NormalExcelConstants;
import com.flyco.poi.excel.entity.ExportParams;
import com.flyco.poi.excel.entity.ImportParams;
import com.flyco.poi.excel.view.EntityExcelView;

import org.apache.shiro.SecurityUtils;
import org.springframework.beans.BeanUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.transaction.annotation.Transactional;
import org.springframework.util.CollectionUtils;
import org.springframework.web.bind.annotation.*;
import org.springframework.web.multipart.MultipartFile;
import org.springframework.web.multipart.MultipartHttpServletRequest;
import org.springframework.web.servlet.ModelAndView;
import com.alibaba.fastjson.JSON;
import io.swagger.annotations.Api;
import io.swagger.annotations.ApiOperation;

/**
 * @Description: 退单明细批次表
 * @Author: flyco
 * @Date: 2023-08-30
 * @Version: V1.0
 */
@Slf4j
@Api(tags = "退单明细批次表")
@RestController
@RequestMapping("/f/returns/omsOrderReturnItemBatch")
public class OmsOrderReturnItemBatchController extends BaseController<OmsOrderReturnItemBatch, IOmsOrderReturnItemBatchService> {
    @Autowired
    private IOmsOrderReturnItemBatchService omsOrderReturnItemBatchService;
    @Autowired
    private IOmsOrderReturnItemService returnItemService;

    /**
     * 分页列表查询
     *
     * @param omsOrderReturnItemBatch
     * @param pageNo
     * @param pageSize
     * @param req
     * @return
     */
    @AutoLog(value = "退单明细批次表-分页列表查询")
    @ApiOperation(value = "退单明细批次表-分页列表查询", notes = "退单明细批次表-分页列表查询")
    @GetMapping(value = "/list")
    public Result<?> queryPageList(OmsOrderReturnItemBatch omsOrderReturnItemBatch,
                                   @RequestParam(name = "pageNo", defaultValue = "1") Integer pageNo,
                                   @RequestParam(name = "pageSize", defaultValue = "10") Integer pageSize,
                                   HttpServletRequest req) {
        QueryWrapper<OmsOrderReturnItemBatch> queryWrapper = QueryGenerator.initQueryWrapper(omsOrderReturnItemBatch, req.getParameterMap());
        Page<OmsOrderReturnItemBatch> page = new Page<OmsOrderReturnItemBatch>(pageNo, pageSize);
        IPage<OmsOrderReturnItemBatch> pageList = omsOrderReturnItemBatchService.page(page, queryWrapper);
        return Result.ok(pageList);
    }

    @AutoLog(value = "退单明细批次表明细")
    @ApiOperation(value = "退单明细批次表明细", notes = "退单明细批次表明细")
    @GetMapping(value = "/returnBatchOrderItem")
    public Result<?> getByApplyId(Long applyId) {
        List<OmsOrderReturnItemBatch> list = omsOrderReturnItemBatchService.getByApplyId(applyId);
        if (!CollectionUtils.isEmpty(list)) {
            list = list.stream().sorted(Comparator.comparing(OmsOrderReturnItemBatch::getProductId)).collect(Collectors.toList());
            List<OmsOrderReturnItemVO> returnItemVOList = new ArrayList<>();
            list.forEach(item -> {
                OmsOrderReturnItemVO itemVO = new OmsOrderReturnItemVO();
                BeanUtils.copyProperties(item, itemVO);
                itemVO.setRealReturnSkuUnitCount(itemVO.getRealUnitQuantity() / itemVO.getProductSkuSpec());
                itemVO.setRealReturnUnitCount(itemVO.getRealUnitQuantity() % itemVO.getProductSkuSpec());
                returnItemVOList.add(itemVO);
            });
            return Result.ok(returnItemVOList);
        }
        return Result.ok(null);
    }

    @AutoLog(value = "删除退货明细")
    @ApiOperation(value = "删除退货明细", notes = "删除退货明细")
    @GetMapping(value = "/deleteItemById/{itemId}")
    public Result<?> deleteItemById(@PathVariable("itemId") Long itemId) {
        Boolean result = omsOrderReturnItemBatchService.removeById(itemId);

        if (result) {
            return Result.ok("删除成功");
        } else {
            return Result.error("删除失败");
        }
    }

    @AutoLog(value = "新增")
    @ApiOperation(value = "新增", notes = "新增")
    @GetMapping(value = "/addItemByItemId/{itemId}")
    public Result<?> addItemByItemId(@PathVariable("itemId") Long itemId) {

        OmsOrderReturnItem itemInfo = returnItemService.getById(itemId);

        OmsOrderReturnItemBatch batchItem = new OmsOrderReturnItemBatch();
        BeanUtils.copyProperties(itemInfo, batchItem);
        batchItem.setId(IdGenerator16Bit.generateId());
        batchItem.setMinUnitQuantity(0);

        Boolean result = omsOrderReturnItemBatchService.save(batchItem);

        if (result) {
            return Result.ok("新增成功");
        } else {
            return Result.error("新增失败");
        }
    }

    @AutoLog(value = "修改")
    @ApiOperation(value = "修改", notes = "修改")
    @PostMapping(value = "/updateBatchItem")
    @Transactional
    public Result<?> updateBatchItem(@RequestBody OrderReturnApproveDTO returnApproveDTO) {

        List<String> errorBatchNo = new ArrayList<>();

        List<OmsOrderReturnItem> returnItemList = returnItemService.getByApplyId(returnApproveDTO.getId());
        Map<Long, OmsOrderReturnItem> itemMap = returnItemList.stream()
                .collect(Collectors.toMap(OmsOrderReturnItem::getId, a -> a));

        //1 需要判断明细和申请表中的总数是否相等，不相等时，告知用户，不进行保存。
        List<OmsOrderReturnItemBatch> itemBatchList = omsOrderReturnItemBatchService.getByApplyId(returnApproveDTO.getId());
        Map<Long, OmsOrderReturnItemBatch> itemBatchMap = itemBatchList.stream()
                .collect(Collectors.toMap(OmsOrderReturnItemBatch::getId, a -> a));
        List<OmsOrderReturnItemBatch> needUpdateBatch = new ArrayList<>();
        if (!CollectionUtils.isEmpty(returnApproveDTO.getItemList())) {
            for (OrderReturnItemDTO item : returnApproveDTO.getItemList()) {
                OmsOrderReturnItemBatch returnItemBatch = itemBatchMap.get(item.getId());
                returnItemBatch.setMinUnitQuantity(item.getReturnSkuUnitCountNotUnit() * returnItemBatch.getProductSkuSpec() + item.getReturnUnitCountNotUnit());
                returnItemBatch.setBatchNo(item.getBatchNo());
                //增加批次号验证，如果批次号不存在，不允许保存
                Boolean isCorrect = batchNoIsCorrect(item.getBatchNo(), returnItemBatch.getProductSkuCode());
                if (!isCorrect) {
                    errorBatchNo.add("物料编码:"+returnItemBatch.getProductSkuCode()+",批次号:"+ item.getBatchNo()+";");
                }
                returnItemBatch.setTotalAmount(new BigDecimal(returnItemBatch.getMinUnitQuantity()).multiply(returnItemBatch.getPrice()));
                needUpdateBatch.add(returnItemBatch);
            }
        }
        if (!CollectionUtils.isEmpty(errorBatchNo)) {
            String errorBatchNoStr = errorBatchNo.stream().collect(Collectors.joining(","));
            return Result.error(errorBatchNoStr + "批次号不正确，请重新输入");
        }

        //一个商品可能会拆分成几个批次号，所以在拆分后的详情中找到该商品的实收数量，跟OmsOrderReturnItem中的该商品进行比较。不相等直接退出。
        Map<Long, List<OmsOrderReturnItemBatch>> itemBatchGroup = needUpdateBatch.stream().collect(Collectors.groupingBy(OmsOrderReturnItemBatch::getProductId));
        for (OmsOrderReturnItem item : returnItemList) {

            List<OmsOrderReturnItemBatch> itemBatches = itemBatchGroup.get(item.getProductId());
            if (CollectionUtils.isEmpty(itemBatches)) {
                if (item.getMinUnitQuantity() > 0) {
                    //说明没有对该商品进行配置
                    return Result.error(item.getProductName() + "改商品拆分后的数量跟退货数量不一致，请重新修改");
                }
            } else {
                Integer batchItemCount = itemBatches.stream().mapToInt(OmsOrderReturnItemBatch::getMinUnitQuantity).sum();
                if (!item.getMinUnitQuantity().equals(batchItemCount) && !item.getMinUnitQuantity().equals(0)) {
                    return Result.error(item.getProductName() + "改商品拆分后的数量跟退货数量不一致，请重新修改");
                }
            }
        }
        omsOrderReturnItemBatchService.updateBatchById(needUpdateBatch);

        //根据批次表再更新退单明细表
        List<OmsOrderReturnItem> needUpdate = new ArrayList<>();
        if (!CollectionUtils.isEmpty(returnApproveDTO.getItemList())) {

            List<OrderReturnItemDTO> returnItemDTOList = returnApproveDTO.getItemList();
            Map<Long, List<OrderReturnItemDTO>> itemDTOByProductIdMap = returnItemDTOList.stream()
                    .collect(Collectors.groupingBy(OrderReturnItemDTO::getProductId));

            for (OmsOrderReturnItem item : returnItemList) {
                OmsOrderReturnItem omsOrderReturnItem = itemMap.get(item.getId());
                List<OrderReturnItemDTO> itemByProduct = itemDTOByProductIdMap.get(item.getProductId());
                if (!CollectionUtils.isEmpty(itemByProduct)) {
                    Integer skuUnitCount = itemByProduct.stream().mapToInt(OrderReturnItemDTO::getReturnSkuUnitCountNotUnit).sum();
                    Integer unitCount = itemByProduct.stream().mapToInt(OrderReturnItemDTO::getReturnUnitCountNotUnit).sum();

                    item.setMinUnitQuantity(skuUnitCount * omsOrderReturnItem.getProductSkuSpec() + unitCount);
                    item.setTotalAmount(new BigDecimal(item.getMinUnitQuantity()).multiply(omsOrderReturnItem.getPrice()));

                    needUpdate.add(item);
                }
            }
        }
        returnItemService.updateBatchById(needUpdate);

        //1 需要判断申请表中，是否有申请数量是0的情况，如果是，需要进行清除。
        List<OmsOrderReturnItem> returnItemList1 = returnItemService.getByApplyId(returnApproveDTO.getId());
        List<Long> needDelList = new ArrayList<>();
        for (OmsOrderReturnItem item : returnItemList1) {
            if (item.getMinUnitQuantity().equals(0)) {
                needDelList.add(item.getId());
            }
        }
        returnItemService.removeByIds(needDelList);


        return Result.ok("更新完成");
    }

    public Boolean batchNoIsCorrect(String batchNo, String skuCode) {

        return omsOrderReturnItemBatchService.batchNoIsCorrect(batchNo, skuCode) > 0 ? true : false;
    }


}
